/*
 * lex.c
 *
 *  Created on: 2009-5-12
 *      Author: hwg
 */


#include"../header/common.h"
/*typedef struct grammer{
	char S;
	statelink 	action;
	LinkList	production;
	LinkList	sentence;
	instack		Sstate;
	cstack		notation;

} grammer;*/
void initles_grammer(grammer *g , char *action ,char * gotos, char *producini , LinkList sentenceini)
{
	g->S = 0;
	ininitian(&(g->state));
	inpush(&(g->state) , 0);
	cinitian(&(g->symbol));
	cpush(&(g->symbol),'!');
	initlist_state(&(g->action) , action);
	initlist_state(&(g->gotos) , gotos);
	initlist_gramexplist(&(g->production) ,producini);
	g->sentence = sentenceini;
}

int grammer_make(grammer *g)
{
	int statenum = 0;
	int senorder = 1;
	int result = 5;
	elmAction cuAction;
	ElemType senelem;
	int i = 12;
	int j=0;
	printf("state\t\t\tsymbol\t\tword\taction\tprodu\tgoto\tmidle\n");
	while(i)
	{
		i--;
		statenum = ingettop(&(g->state));

		printf("[");
		j = 0;
		while(j<g->state.top)
		{
			printf("%d",g->state.stack[j]);
			j++;
		}
		printf("]");
		printf("\t\t\t[");
		j = 0;
		while(j<g->symbol.top)
		{
			printf("%c",g->symbol.stack[j]);
			j++;
		}
		printf("]");


		j = senorder;
		printf("\t\t[");
		while(getWord_Sq(g->sentence, j,  &senelem)==ok)
		{
			printf("%c",senelem.uniwordnode.exp[0]);
			j++;
		}
		printf("]");

		getWord_Sq(g->sentence, senorder,  &senelem);
		result = getAction_st(g->action , statenum ,senelem.uniwordnode.exp[0] , &cuAction);
		if(result == error)
		{
			return error;
		}
		else
		{
			printf("\t%c%d",cuAction.action,cuAction.number);
			//printf("\ncrent setence %c\t",senelem.uniwordnode.exp[0]);
			if(cuAction.action == 'A')
				break;
			else
			{
				if(cuAction.action == 'S')
				{
					inpush(&(g->state) , cuAction.number);
					//printf("the action is S cuAction.number%d",cuAction.number);
					cpush(&(g->symbol),senelem.uniwordnode.exp[0]);
					putchar('\n');
					senorder = senorder + 1;
				}
				else
				{
					//printf("the action is R cuAction.number%d",cuAction.number);
					//putchar(cuAction.action);
					agreement(g, cuAction , &senorder);
				}

			}
		}

	}
	return ok;
}

int agreement(grammer *g ,elmAction cuAction ,int *senorder)
{
	ElemType prod;
	int i = 0;
	int result = 5;
	if(Listgetnode(g->production , cuAction.number+1 , &prod) == error)
		return error;
	else
	{
		printf("\t%s",prod.uniproduction.express);
		while(prod.uniproduction.express[i] != '\0')//规约
		{
			cpop(&(g->symbol));
			inpop(&(g->state));
			i = i+ 1;
		}
		cpush(&(g->symbol) , prod.uniproduction.h);//GOTO

		result = getAction_st(g->gotos ,ingettop(&(g->state)), prod.uniproduction.h, &cuAction);
		if(result == error)
			return error;
		else
		{
			printf("\t G%d\t%s\n",cuAction.go,prod.uniproduction.middlecode);
			inpush(&(g->state) , cuAction.go);
		}

		return ok;
	}
}
